package org.ejc.api.executive;

import java.util.List;

import javax.ejb.SessionBean;
import javax.naming.NamingException;

import org.apache.log4j.Category;
import org.ejc.business.login.ExecutiveValidation;
import org.ejc.datatype.executive.ExecutiveSearchCriteria;
import org.ejc.exception.EJCPersistenceException;
import org.ejc.persist.model.ConventionExecutive;
import org.ejc.persist.model.ConventionRegistrant;
import org.ejc.util.EJCUtils;
import org.hibernate.Criteria;
import org.hibernate.Session;
import org.hibernate.Transaction;
import org.hibernate.criterion.Expression;

/**
 * @author Brian Boyle
 * 
 * @ejb.bean type="Stateless" name="ConventionExecutiveAPI"
 *           description="ConventionExecutiveAPI session bean"
 *           local-jndi-name="org.ejc/ConventionExecutiveAPILocalHome"
 *           jndi-name="org.ejc/ConventionExecutiveAPIHome" view-type="both"
 * 
 * @ejb.ejb-ref ejb-name="ConventionExecutiveAPI"
 *              ref-name="ejb/ConventionExecutiveAPI" view-type="both"
 * 
 * @ejb.transaction type="RequiresNew"
 * @ejb.util generate = "physical"
 */
public abstract class ConventionExecutiveAPIBean implements SessionBean {

	Category log = Category.getInstance(ConventionExecutiveAPIBean.class);

	/**
	 * Retrieve an executive based on the username entered via the login screen.
	 * 
	 * @param username
	 * @return The ConventionExecutive object for that username
	 * @throws NamingException
	 * @throws EJCPersistenceException
	 * @ejb.interface-method view-type="both"
	 */
	public ConventionExecutive getExecutive(String username)
			throws NamingException, EJCPersistenceException {
		Session hsession = null;
		try {
			hsession = EJCUtils.getHibernateSession();
			ConventionExecutive executive = (ConventionExecutive) hsession
					.createCriteria(ConventionExecutive.class).add(
							Expression.eq("username", username)).uniqueResult();

			hsession.close();
			return executive;

		} finally {
			if (hsession != null) {
				hsession.close();
			}
		}
	}

	/**
	 * @ejb.interface-method view-type="both"
	 */
	public ConventionExecutive getExecutive(Integer execId)
			throws NamingException, EJCPersistenceException {
		Session hsession = null;
		ConventionExecutive exec = new ConventionExecutive();
		try {
			hsession = EJCUtils.getHibernateSession();
			ConventionExecutive executive = (ConventionExecutive) hsession
					.load(ConventionExecutive.class, execId);
			exec.setExecutiveId(execId);
			exec.setFirstName(executive.getFirstName());
			exec.setLastName(executive.getLastName());
			exec.setAdmin(executive.isAdmin());
			exec.setUsername(executive.getUsername());
			exec.setLanguageIso(executive.getLanguageIso());
			exec.setPassWord(executive.getPassWord());
		} catch (Exception e) {
			log.fatal(e);
		} finally {
			if (hsession != null) {
				hsession.close();
			}
		}
		return exec;
	}

	/**
	 * @ejb.interface-method view-type="both"
	 */
	public Integer  createConventionExecutive(
			ConventionExecutive exec) throws NamingException,
			EJCPersistenceException {
		Session hsession = null;
		Transaction tx = null;
		try {
			hsession = EJCUtils.getHibernateSession();
			tx = hsession.beginTransaction();

			Integer id = (Integer) hsession.save(exec);
			log.fatal("Id is " + id);
			tx.commit();
			hsession.flush();
			return id;
		} catch (Exception e) {
			log.fatal(e);
		} finally {
			if (hsession != null) {
				hsession.close();
			}
		}
		return null;
	}

	/**
	 * @ejb.interface-method view-type="both"
	 */
	public void updateConventionExecutive(ConventionExecutive exec)
			throws NamingException, EJCPersistenceException {
		Session hsession = null;
		Transaction tx = null;
		try {
			hsession = EJCUtils.getHibernateSession();
			tx = hsession.beginTransaction();
			ConventionExecutive execFromDb = (ConventionExecutive) hsession
					.load(ConventionExecutive.class, exec.getExecutiveId());

			execFromDb.setFirstName(exec.getFirstName());
			execFromDb.setLastName(exec.getLastName());
			execFromDb.setLanguageIso(exec.getLanguageIso());
			execFromDb.setPassWord(exec.getPassWord());
			tx = hsession.beginTransaction();
			hsession.update(execFromDb);
			tx.commit();
			hsession.flush();
		} catch (Exception e) {
			log.fatal(e);
		} finally {
			if (hsession != null) {
				hsession.close();
			}
		}

	}

	/**
	 * Search for an Executive.
	 * @ejb.interface-method view-type="both"
	 */
	public List searchExecutives(ExecutiveSearchCriteria searchCriteria, int minResult, int maxResult)
	{
		Session hsession = null;
		List executives = null;
		try {
			hsession = EJCUtils.getHibernateSession();
			log.debug("Searching for executives");
			Criteria execCrit = hsession.createCriteria(ConventionExecutive.class);
			if(searchCriteria.getFirstName() != null && searchCriteria.getFirstName().length() != 0){
				execCrit.add(Expression.like("firstName", "%"+searchCriteria.getFirstName()+"%"));
			}
			if(searchCriteria.getLastName() != null && searchCriteria.getLastName().length() != 0){
				execCrit.add(Expression.like("lastName", "%"+searchCriteria.getLastName()+"%"));
			}
			if(searchCriteria.getUserName() != null && searchCriteria.getUserName().length() != 0){
				execCrit.add(Expression.like("username", "%"+searchCriteria.getUserName()+"%"));
			}
			if(searchCriteria.getAdmin()){
				execCrit.add(Expression.eq("admin", "1"));
			}
			executives = execCrit.setFirstResult(minResult).setMaxResults(maxResult).list();
			log.debug("Returning a list of executives");
		} catch (EJCPersistenceException e) {
			log.fatal("Error in getting list of executives");
			e.printStackTrace();
		}
		hsession.close();
		
		return executives;
	}
	
	/**
	 * Validate an executive's password for login.
	 * 
	 * @param inputPassword
	 *            The password that was input via the login screen.
	 * @param executivePassword
	 *            The executive's password
	 * @return True if the passwords match. False if they dont.
	 * @ejb.interface-method view-type="both"
	 */
	public boolean validatePassword(String inputPassword,
			String executivePassword) {
		ExecutiveValidation execValidation = new ExecutiveValidation();
		return execValidation
				.validatePassword(inputPassword, executivePassword);
	}
}
